﻿using MQTTnet;
using MQTTnet.Client;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
using NLog;
using SqlSugar;
using System.Collections.Concurrent;
using System.Text;
using MqttToDatabase.Table2;


namespace MqttToDatabase
{
    /// <summary>
    /// MqttClientService 负责管理 MQTT 客户端的连接、订阅、消息处理和动态批量写入数据库。
    /// 使用 BlockingCollection 实现消息队列，支持动态调整批量大小和时间窗口。
    public class MqttClientService
    {
        private IMqttClient _mqttClient;
        private bool _mqttIsConnected = false; // 标记 MQTT 客户端是否已连接
        private static readonly Logger Logger = LogManager.GetCurrentClassLogger(); // NLog 日志记录器

        private readonly BlockingCollection<JObject> _messageQueue; // 消息队列，用于暂存接收到的消息
        private int _currentBatchSize = 100; // 当前动态批量大小（默认值为 100）
        private int _currentTimeWindow = 5000; // 当前动态时间窗口（毫秒）（默认值为 5s）
        private readonly int _maxBatchSize = 500; // 最大批量大小
        private readonly int _minBatchSize = 50;  // 最小批量大小
        private readonly int _maxTimeWindow = 10000; // 最大时间窗口（10秒）
        private readonly int _minTimeWindow = 1000;  // 最小时间窗口（1秒）

        private readonly DatabaseService _databaseService; // 数据库服务实例，用于将消息写入数据库

        /// <summary>
        /// 初始化 MqttClientService 实例。
        /// 设置消息队列的最大容量为 1000，初始化 MQTT 客户端并绑定事件处理器。
        public MqttClientService(DatabaseService databaseService)
        {
            // 设置 BlockingCollection 的最大容量为 1000
            _messageQueue = new BlockingCollection<JObject>(new ConcurrentQueue<JObject>(), 1000);
            _mqttClient = new MqttFactory().CreateMqttClient();
            _mqttClient.ConnectedAsync += MqttClient_ConnectedAsync;
            _mqttClient.ApplicationMessageReceivedAsync += MqttClient_ApplicationMessageReceivedAsync;

            _databaseService = databaseService;
        }

        /// <summary>
        /// 处理接收到的 MQTT 消息。
        /// 解析消息内容，提取时间戳和参数，并将其加入消息队列。
        private async Task MqttClient_ApplicationMessageReceivedAsync(MqttApplicationMessageReceivedEventArgs e)
        {
            if (e.ApplicationMessage.Retain)
            {
                Logger.Info("忽略保留消息");
                return;
            }

            byte[] data = e.ApplicationMessage.PayloadSegment.ToArray();
            string messagePayload = Encoding.UTF8.GetString(data);

            try
            {
                JObject jsonMessage = JObject.Parse(messagePayload);
                if (!_messageQueue.TryAdd(jsonMessage, TimeSpan.FromMilliseconds(100)))
                {
                    Logger.Error("消息队列已满，无法添加新消息。");
                    return;
                }
                Logger.Debug($"当前队列大小: {_messageQueue.Count}, 批量大小: {_currentBatchSize}");

                // **触发数据库插入**
                if (_messageQueue.Count >= _currentBatchSize)
                {
                    Logger.Debug("队列已达到批量大小，开始写入数据库...");
                    await FlushQueueToDatabaseAsync();
                }

            }
            catch (JsonException jex)
            {
                Logger.Error(jex, $"JSON 解析失败。Topic: {e.ApplicationMessage.Topic}, 原始消息: {messagePayload}");
            }
            catch (Exception ex)
            {
                Logger.Error(ex.ToString());  // 记录完整异常信息
                Logger.Error(ex, $"处理消息时发生未知错误。Topic: {e.ApplicationMessage.Topic}, 原始消息: {messagePayload}");
            }
        }

        /// <summary>
        /// 将消息队列中的数据批量写入数据库。
        private async Task FlushQueueToDatabaseAsync()
        {
            // 初始化一个列表来存储从队列中取出的消息
            var messages = new List<JObject>();

            // 从消息队列中消费消息，直到达到当前批处理大小
            foreach (var message in _messageQueue.GetConsumingEnumerable())
            {
                messages.Add(message);
                // 如果收集的消息数量达到当前批处理大小，则停止获取更多消息
                if (messages.Count >= _currentBatchSize) break; // 使用动态批量大小
            }

            // 如果收集到了消息，则执行数据库写入操作
            if (messages.Any())
            {
                // 记录开始写入数据库的时间
                var startTime = DateTime.Now;

                // 异步将消息写入数据库
                await _databaseService.WriteToDatabaseAsync(messages);

                // 计算写入数据库所花费的时间
                var duration = DateTime.Now - startTime;

                // 根据写入数据库的处理时间和队列中剩余的消息数量调整参数
                AdjustParameters(duration, _messageQueue.Count);
            }

        }

        /// <summary>
        /// 异步连接到 MQTT 服务器。
        /// /// </summary>
        public async Task ConnectAsync(string ip, int port, string clientId, string username, string password)
        {
            var options = new MqttClientOptionsBuilder()
                .WithTcpServer(ip, port)
                .WithClientId(clientId)
                .WithCredentials(username, password)
                .WithCleanSession(true)
                .WithTimeout(TimeSpan.FromSeconds(30)) // 设置通信超时
                .Build();

            await _mqttClient.ConnectAsync(options, CancellationToken.None);
        }

        public async Task DisconnectAsync()
        {
            if (_mqttIsConnected)
            {
                await _mqttClient.DisconnectAsync();
            }
        }

        private async Task MqttClient_ConnectedAsync(MqttClientConnectedEventArgs e)
        {
            Logger.Info("MQTT 客户端连接成功");
            _mqttIsConnected = true;
            await _mqttClient.SubscribeAsync("toServer");
            await _mqttClient.SubscribeAsync("toServer/+");
        }

        /// <summary>
        /// 根据写入数据库的耗时和队列中剩余的消息数量动态调整批量大小和时间窗口。
        /// </summary>
        private void AdjustParameters(TimeSpan duration, int remainingMessages)
        {
            // 调整策略：处理快且队列积压则增加吞吐量，反之减少
            if (duration.TotalMilliseconds < 1000 && remainingMessages > _currentBatchSize * 2)
            {
                _currentBatchSize = Math.Min(_currentBatchSize + 50, _maxBatchSize);
                _currentTimeWindow = Math.Max(_currentTimeWindow - 1000, _minTimeWindow);
            }
            else if (duration.TotalMilliseconds > 2000 || remainingMessages < _currentBatchSize)
            {
                _currentBatchSize = Math.Max(_currentBatchSize - 50, _minBatchSize);
                _currentTimeWindow = Math.Min(_currentTimeWindow + 1000, _maxTimeWindow);
            }
        }
    }

    public class DatabaseService
    {
        private static readonly Logger Logger = LogManager.GetCurrentClassLogger();
        private readonly SqlSugarScope _sqlSugar;
        private readonly SemaphoreSlim _dbLock = new(1, 1); // 异步锁

        private string _currentTableNameIO;
        private string _currentTableNameNetPort;
        private string _currentTableNameSerial;

        static List<string> a1 = new List<string>();//串口采集的设备
        static List<string> a2 = new List<string>();//网口监听采集的设备
        static List<string> a31 = new List<string>();//IO1采集的设备
        static List<string> a32 = new List<string>();//IO2采集的设备
        public static Dictionary<string, int> nameToDeviceIdMap { set; get; }


        public DatabaseService(SqlSugarScope sqlSugar)
        {
            _sqlSugar = sqlSugar;
            _currentTableNameIO = GetCurrentTableNameIO(DateTime.Now);
            _currentTableNameNetPort = GetCurrentTableNameNetPort(DateTime.Now);
            _currentTableNameSerial = GetCurrentTableNameSerial(DateTime.Now);

            // 使用异步定时器初始化
            _ = InitializeTimerAsync();

            var DeviceData = _sqlSugar.Queryable<device>().ToList();
            nameToDeviceIdMap = DeviceData.ToDictionary(item => item.name, item => item.deviceid);
            a1 = DeviceData.Where(i => i.remarks == "串口").Select(a => a.name).ToList();
            a2 = DeviceData.Where(i => i.remarks == "网口监听").Select(a => a.name).ToList();
            a31 = DeviceData.Where(i => i.remarks == "IO1").Select(a => a.name).ToList();
            a32 = DeviceData.Where(i => i.remarks == "IO2").Select(a => a.name).ToList();
        }

        private async Task InitializeTimerAsync()
        {
            while (true)
            {
                DateTime now = DateTime.Now;
                DateTime nextMidnight = now.Date.AddDays(1).AddSeconds(1);
                TimeSpan delay = nextMidnight - now;

                Logger.Info($"下次切换时间: {nextMidnight}, 剩余延迟: {delay}");
                await Task.Delay(delay);

                // 触发时重新获取实时时间
                DateTime triggerTime = DateTime.Now;
                Logger.Info($"定时器触发于: {triggerTime}");
                await CheckAndSwitchTableAsync(triggerTime);
            }
        }

        private static readonly DateTime StartDate = new DateTime(2025, 3, 25); // 固定起点
        private string GetCurrentTableNameIO(DateTime time)
        {
            //每天切换一次表，IO 数据循环使用 8 个表 
            int totalDays = (time.Date - StartDate.Date).Days;
            int tableIndex = (totalDays % 8) + 1; // 8表循环
            return $"iodevicedata_{tableIndex}";
        }

        private string GetCurrentTableNameNetPort(DateTime time)
        {
            int totalDays = (time.Date - StartDate.Date).Days;
            int tableIndex = (totalDays % 8) + 1; // 8表循环
            return $"netportdevicedata_{tableIndex}";
        }

        private string GetCurrentTableNameSerial(DateTime time)
        {
            int totalDays = (time.Date - StartDate.Date).Days;
            int tableIndex = (totalDays % 8) + 1; // 8表循环
            return $"serialdevicedata_{tableIndex}";
        }

        private async Task CheckAndSwitchTableAsync(DateTime now)
        {
            await _dbLock.WaitAsync();
            try
            {
                string newTableNameIO = GetCurrentTableNameIO(now);
                string newTableNameNetPort = GetCurrentTableNameNetPort(now);
                string newTableNameSerial = GetCurrentTableNameSerial(now);
                if (newTableNameIO != _currentTableNameIO)
                {
                    await ClearTable(newTableNameIO);
                    _currentTableNameIO = newTableNameIO;
                    Logger.Info($"切换到表 {_currentTableNameIO}");
                }
                if (newTableNameNetPort != _currentTableNameNetPort)
                {
                    await ClearTable(newTableNameNetPort);
                    _currentTableNameNetPort = newTableNameNetPort;
                    Logger.Info($"切换到表 {_currentTableNameNetPort}");
                }
                if (newTableNameSerial != _currentTableNameSerial)
                {
                    await ClearTable(newTableNameSerial);
                    _currentTableNameSerial = newTableNameSerial;
                    Logger.Info($"切换到表 {_currentTableNameSerial}");
                }
            }
            finally
            {
                _dbLock.Release();
            }
        }

        private async Task ClearTable(string tableName)
        {
            await _sqlSugar.Ado.ExecuteCommandAsync($"TRUNCATE TABLE `{tableName}`;");
            Logger.Info($"已清空表: {tableName}");
        }


        public async Task WriteToDatabaseAsync(List<JObject> messages)
        {
            foreach (var root in messages)
            {
                try
                {
                    string dname = root["deviceName"]?.ToString();
                    //if (string.IsNullOrEmpty(dname))
                    //{
                    //    //Logger.Warn("deviceName 为空，跳过此消息。");
                    //    // 新增：输出消息内容或关键字段
                    //    Logger.Warn($"deviceName 为空，跳过此消息。消息内容: {root.ToString(Formatting.None)}");
                    //    continue;
                    //}
                    // 其他逻辑...
                    #region 第三类 IO采集
                    if (a31.Contains(dname))
                    {
                        iodevicedata tidata = new iodevicedata();
                        bool issave = false;
                        foreach (var item in root["data"])
                        {
                            var v = item["value"];
                            switch (item["name"].ToString())
                            {
                                case string s when s == (dname + ":" + "开模"):
                                    if (Convert.ToInt16(v) == 1)
                                    {
                                        tidata.kai = true;
                                    }
                                    break;
                            }
                        }
                        tidata.deviceid = nameToDeviceIdMap[dname];
                        tidata.time = Convert.ToInt32(root["uploadTimestamp"]);
                        if (tidata.kai == true)
                        {
                            await _sqlSugar.Insertable(tidata).AS(_currentTableNameIO).ExecuteCommandAsync();
                        }
                    }
                    else if (a32.Contains(dname))
                    {
                        iodevicedata tidata = new iodevicedata();
                        foreach (var item in root["data"])
                        {
                            var v = item["value"];
                            switch (item["name"].ToString())
                            {
                                case string s when s == (dname + ":" + "开模"):
                                    if (Convert.ToInt16(v) == 0)
                                    {
                                        tidata.kai = true;
                                    }
                                    break;
                                case string s when s == (dname + ":" + "合模"):
                                    if (Convert.ToInt16(v) == 0)
                                    {
                                        tidata.he = true;
                                    }
                                    break;
                            }
                        }
                        tidata.deviceid = nameToDeviceIdMap[dname];
                        tidata.time = Convert.ToInt32(root["uploadTimestamp"]);
                        if (tidata.kai == true || tidata.he == true)
                        {
                            await _sqlSugar.Insertable(tidata).AS(_currentTableNameIO).ExecuteCommandAsync();
                        }
                    }
                    #endregion
                    #region 第二类 网口采集
                    else if (a2.Contains(dname))//&& Convert.ToInt32(root["uploadTimestamp"]) >= dnameandoldtime.a1dic[root["deviceName"].ToString()] + 20)
                    {
                        netportdevicedata tndata = new netportdevicedata();
                        foreach (var item in root["data"])
                        {
                            var v = item["value"];
                            switch (item["name"].ToString())
                            {
                                case string s when s == (dname + ":" + "OPM"):
                                    tndata.status = Convert.ToInt32(v);
                                    break;
                                case string s when s == (dname + ":" + "T1"):
                                    tndata.HT_Temp_1 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "T2"):
                                    tndata.HT_Temp_2 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "T3"):
                                    tndata.HT_Temp_3 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "T4"):
                                    tndata.HT_Temp_4 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "T5"):
                                    tndata.HT_Temp_5 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "T6"):
                                    tndata.HT_Temp_6 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "T7"):
                                    tndata.HT_Temp_7 = Convert.ToSingle(v);
                                    break;


                                case string s when s == (dname + ":" + "CNT"):
                                    tndata.cnt = Convert.ToInt32(v);
                                    break;
                                case string s when s == (dname + ":" + "CYCN"):
                                    tndata.cycn = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "CT")://冷却时间
                                    tndata.HT_Colling_time = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "EIPT")://射出时间
                                    tndata.HT_Shot_time = Convert.ToSingle(v);
                                    break;

                                case string s when s == (dname + ":" + "PP1")://保压压力1
                                    tndata.HT_hp_pressure_1 = Convert.ToInt32(v);
                                    break;
                                case string s when s == (dname + ":" + "PP2"):
                                    tndata.HT_hp_pressure_2 = Convert.ToInt32(v);
                                    break;
                                case string s when s == (dname + ":" + "PP3"):
                                    tndata.HT_hp_pressure_3 = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "PV1"):  //  保压速度1
                                    tndata.HT_hp_speed_1 = Convert.ToInt32(v);
                                    break;
                                case string s when s == (dname + ":" + "PV2"):
                                    tndata.HT_hp_speed_2 = Convert.ToInt32(v);
                                    break;
                                case string s when s == (dname + ":" + "PV3"):
                                    tndata.HT_hp_speed_3 = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "PT1")://保压时间1
                                    tndata.HT_hp_time_1 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "PT2"):
                                    tndata.HT_hp_time_2 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "PT3"):
                                    tndata.HT_hp_time_3 = Convert.ToSingle(v);
                                    break;

                                case string s when s == (dname + ":" + "SBS1")://射退位置
                                    tndata.HT_shot_back_pos = Convert.ToSingle(v);
                                    break;


                                case string s when s == (dname + ":" + "IS1")://射出（注射）位置1
                                    tndata.HT_shot_pos_1 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "IS2"):
                                    tndata.HT_shot_pos_2 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "IS3"):
                                    tndata.HT_shot_pos_3 = Convert.ToSingle(v);
                                    break;

                                case string s when s == (dname + ":" + "IP1")://射出压力1
                                    tndata.HT_shot_pressure_1 = Convert.ToInt32(v);
                                    break;
                                case string s when s == (dname + ":" + "IP2"):
                                    tndata.HT_shot_pressure_2 = Convert.ToInt32(v);
                                    break;
                                case string s when s == (dname + ":" + "IP3"):
                                    tndata.HT_shot_pressure_3 = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "IV1")://射出速度1
                                    tndata.HT_shot_speed_1 = Convert.ToInt32(v);
                                    break;
                                case string s when s == (dname + ":" + "IV2"):
                                    tndata.HT_shot_speed_2 = Convert.ToInt32(v);
                                    break;
                                case string s when s == (dname + ":" + "IV3"):
                                    tndata.HT_shot_speed_3 = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "PLBP1")://储料背压
                                    tndata.HT_storage_B_pressure_1 = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "PLS1")://储料位置1
                                    tndata.HT_storage_pos_1 = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "PLP1")://储料压力1
                                    tndata.HT_storage_pressure_1 = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "PLV1")://储料速度1
                                    tndata.HT_storage_speed_1 = Convert.ToInt32(v);
                                    break;

                                //20250506新增需求
                                case string s when s == (dname + ":" + "ECYCT"):
                                    tndata.ECYCT = Convert.ToSingle(v);
                                    break;

                                case string s when s == (dname + ":" + "EIPM"):
                                    tndata.EIPM = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "EIPSE"):
                                    tndata.EIPSE = Convert.ToSingle(v);
                                    break;

                                case string s when s == (dname + ":" + "EIPT"):
                                    tndata.EIPT = Convert.ToSingle(v);
                                    break;

                                case string s when s == (dname + ":" + "EISS"):
                                    tndata.EISS = Convert.ToSingle(v);
                                    break;

                                case string s when s == (dname + ":" + "EIVM"):
                                    tndata.EIVM = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "EPLSPM"):
                                    tndata.EPLSPM = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "EPLST"):
                                    tndata.EPLST = Convert.ToSingle(v);
                                    break;

                                case string s when s == (dname + ":" + "ESIPP"):
                                    tndata.ESIPP = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "ESIPS"):
                                    tndata.ESIPS = Convert.ToSingle(v);
                                    break;

                                case string s when s == (dname + ":" + "ESIPT"):
                                    tndata.ESIPT = Convert.ToSingle(v);
                                    break;

                                case string s when s == (dname + ":" + "ET1"):
                                    tndata.ET1 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "ET2"):
                                    tndata.ET2 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "ET3"):
                                    tndata.ET3 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "ET4"):
                                    tndata.ET4 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "ET5"):
                                    tndata.ET5 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "ET6"):
                                    tndata.ET6 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "ET7"):
                                    tndata.ET7 = Convert.ToSingle(v);
                                    break;


                                default:
                                    //if (Convert.ToInt32(item["value"])!=0)
                                    //tndata.other += item["name"] + ":" + item["value"]+";";
                                    break;
                            }
                            #region 测试
                            //if (dname == dname + ":" + "OPM")
                            //{
                            //    tdata.status = Convert.ToInt32(item["value"]);
                            //}
                            //if (dname == dname + ":" + "T1")
                            //{
                            //    tdata.HT_Temp_1 = Convert.ToInt32(item["value"]);
                            //}
                            //if (dname == dname + ":" + "T2")
                            //{
                            //    tdata.HT_Temp_2 = Convert.ToInt32(item["value"]);
                            //}
                            //if (dname == dname + ":" + "T3")
                            //{
                            //    tdata.HT_Temp_3 = Convert.ToInt32(item["value"]);
                            //}
                            //if (dname == dname + ":" + "T4")
                            //{
                            //    tdata.HT_Temp_4 = Convert.ToInt32(item["value"]);
                            //}
                            //if (dname == dname + ":" + "T5")
                            //{
                            //    tdata.HT_Temp_5 = Convert.ToInt32(item["value"]);
                            //}
                            //if (dname == dname + ":" + "CNT")
                            //{
                            //    tdata.cnt = Convert.ToInt32(item["value"]);
                            //}
                            #endregion
                        }
                        tndata.deviceid = nameToDeviceIdMap[dname];
                        tndata.time = Convert.ToInt32(root["uploadTimestamp"]);
                        //dnameandoldtime.a1dic[tdata.id] = Convert.ToInt32(root["uploadTimestamp"]);
                        await _sqlSugar.Insertable(tndata).AS(_currentTableNameNetPort).ExecuteCommandAsync();
                    }
                    #endregion
                    #region 第一类 串口
                    if (a1.Contains(dname))
                    {
                        serialdevicedata tsdata = new serialdevicedata();
                        int value;
                        foreach (var item in root["data"])
                        {
                            var v = item["value"];
                            switch (item["name"].ToString())
                            {
                                case string s when s == (dname + ":" + "HT_Temp_1"):
                                    tsdata.HT_Temp_1 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_Temp_2"):
                                    tsdata.HT_Temp_2 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_Temp_3"):
                                    tsdata.HT_Temp_3 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_Temp_4"):
                                    tsdata.HT_Temp_4 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_Temp_5"):
                                    tsdata.HT_Temp_5 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_Temp_6"):
                                    tsdata.HT_Temp_6 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_Temp_7"):
                                    tsdata.HT_Temp_7 = Convert.ToSingle(v);
                                    break;

                                case string s when s == (dname + ":" + "HT_mold_cool_time")://冷却时间
                                    tsdata.HT_Colling_time = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_Shot_time")://射出时间
                                    tsdata.HT_Shot_time = Convert.ToSingle(v);
                                    break;

                                case string s when s == (dname + ":" + "HT_hp_pressure_1")://保压压力1
                                    tsdata.HT_hp_pressure_1 = Convert.ToInt32(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_hp_pressure_2"):
                                    tsdata.HT_hp_pressure_2 = Convert.ToInt32(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_hp_pressure_3"):
                                    tsdata.HT_hp_pressure_3 = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "HT_hp_speed_1"):  //  保压速度1
                                    tsdata.HT_hp_speed_1 = Convert.ToInt32(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_hp_speed_2"):
                                    tsdata.HT_hp_speed_2 = Convert.ToInt32(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_hp_speed_3"):
                                    tsdata.HT_hp_speed_3 = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "HT_hp_time_1")://保压时间1
                                    tsdata.HT_hp_time_1 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_hp_time_2"):
                                    tsdata.HT_hp_time_2 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_hp_time_3"):
                                    tsdata.HT_hp_time_3 = Convert.ToSingle(v);
                                    break;

                                case string s when s == (dname + ":" + "HT_shot_back_pos")://射退位置
                                    tsdata.HT_shot_back_pos = Convert.ToSingle(v);
                                    break;

                                case string s when s == (dname + ":" + "HT_shot_pos_1")://射出（注射）位置1
                                    tsdata.HT_shot_pos_1 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_shot_pos_2"):
                                    tsdata.HT_shot_pos_2 = Convert.ToSingle(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_shot_pos_3"):
                                    tsdata.HT_shot_pos_3 = Convert.ToSingle(v);
                                    break;

                                case string s when s == (dname + ":" + "HT_shot_pressure_1")://射出压力1
                                    tsdata.HT_shot_pressure_1 = Convert.ToInt32(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_shot_pressure_2"):
                                    tsdata.HT_shot_pressure_2 = Convert.ToInt32(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_shot_pressure_3"):
                                    tsdata.HT_shot_pressure_3 = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "HT_shot_speed_1")://射出速度1
                                    tsdata.HT_shot_speed_1 = Convert.ToInt32(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_shot_speed_2"):
                                    tsdata.HT_shot_speed_2 = Convert.ToInt32(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_shot_speed_3"):
                                    tsdata.HT_shot_speed_3 = Convert.ToInt32(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_status"):
                                    tsdata.status = Convert.ToInt32(v);
                                    break;
                                case string s when s == (dname + ":" + "HT_prod_num"):
                                    tsdata.cnt = Convert.ToInt32(v);
                                    break;

                                //20250506新增需求
                                case string s when s == (dname + ":" + "HT_prod_num"):
                                    tsdata.cnt = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "HT_pressure"):
                                    tsdata.HT_pressure = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "HT_speed"):
                                    tsdata.HT_speed = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "HT_B_pressure"):
                                    tsdata.HT_B_pressure = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "HT_Injec_pos"):
                                    tsdata.HT_Injec_pos = Convert.ToSingle(v);
                                    break;

                                case string s when s == (dname + ":" + "HT_Shot_start_point_pos"):
                                    tsdata.HT_Shot_start_point_pos = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "HT_HP_switch_pos"):
                                    tsdata.HT_HP_switch_pos = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "HT_Shot_end_point_pos"):
                                    tsdata.HT_Shot_end_point_pos = Convert.ToInt32(v);
                                    break;

                                case string s when s == (dname + ":" + "HT_Shot_monitor_pos"):
                                    tsdata.HT_Shot_monitor_pos = Convert.ToInt32(v);
                                    break;

                                default:
                                    if (int.TryParse(item["value"].ToString(), out value) && value != 0 && value != 65535)
                                    {

                                        //tsdata.other += item["name"] + ":" + item["value"] + ";";

                                        if (item["name"].ToString().Contains("HT_storage_B_pressure"))
                                        {
                                            tsdata.HT_storage_B_pressure_n = Convert.ToInt32(v);
                                        }
                                        else if (item["name"].ToString().Contains("HT_storage_pos"))
                                        {
                                            tsdata.HT_storage_pos_n = Convert.ToInt32(v);
                                        }
                                        else if (item["name"].ToString().Contains("HT_storage_pressure"))
                                        {
                                            tsdata.HT_storage_pressure_n = Convert.ToInt32(v);
                                        }
                                        else if (item["name"].ToString().Contains("HT_storage_speed"))
                                        {
                                            tsdata.HT_storage_speed_n = Convert.ToInt32(v);
                                        }
                                    }
                                    break;
                            }
                        }
                        tsdata.deviceid = nameToDeviceIdMap[dname];
                        tsdata.time = Convert.ToInt32(root["uploadTimestamp"]);
                        await _sqlSugar.Insertable(tsdata).AS(_currentTableNameSerial).ExecuteCommandAsync();
                    }
                    #endregion
                }
                catch (Exception ex)
                {
                    Logger.Error(ex, $"处理消息时发生错误: {root}");
                }
            }

        }

    }
}